MUTTER_MIN_VERSION=3.2.1
FOLKS_MIN_VERSION=0.5.2
GTK_MIN_VERSION=3.0.0
-GLIB_MIN_VERSION=2.31.0
-GIO_MIN_VERSION=2.29.10
+GIO_MIN_VERSION=2.31.0
LIBECAL_MIN_VERSION=2.32.0
LIBEDATASERVER_MIN_VERSION=1.2.0
LIBEDATASERVERUI_MIN_VERSION=2.91.6
STARTUP_NOTIFICATION_MIN_VERSION=0.11
# Collect more than 20 libraries for a prize!
-PKG_CHECK_MODULES(GNOME_SHELL, glib-2.0 >= $GLIB_MIN_VERSION
- gio-2.0 >= $GIO_MIN_VERSION
- gio-unix-2.0 dbus-glib-1 libxml-2.0
+PKG_CHECK_MODULES(GNOME_SHELL, gio-unix-2.0 >= $GIO_MIN_VERSION
+ libxml-2.0
gtk+-3.0 >= $GTK_MIN_VERSION
folks >= $FOLKS_MIN_VERSION
libmutter >= $MUTTER_MIN_VERSION
// -*- mode: js; js-indent-level: 4; indent-tabs-mode: nil -*-
const Clutter = imports.gi.Clutter;
-const DBus = imports.dbus;
const Gdk = imports.gi.Gdk;
const Gio = imports.gi.Gio;
const GLib = imports.gi.GLib;
Gio.DesktopAppInfo.set_desktop_env('GNOME');
shellDBusService = new ShellDBus.GnomeShell();
- // Force a connection now; dbus.js will do this internally
- // if we use its name acquisition stuff but we aren't right
- // now; to do so we'd need to convert from its async calls
- // back into sync ones.
- DBus.session.flush();
// Ensure ShellWindowTracker and ShellAppUsage are initialized; this will
// also initialize ShellAppSystem first. ShellAppSystem
// -*- mode: js; js-indent-level: 4; indent-tabs-mode: nil -*-
-const DBus = imports.dbus;
const Lang = imports.lang;
+const Gio = imports.gi.Gio;
+const GLib = imports.gi.GLib;
const Config = imports.misc.config;
const ExtensionSystem = imports.ui.extensionSystem;
const Main = imports.ui.main;
-const GnomeShellIface = {
- name: 'org.gnome.Shell',
- methods: [{ name: 'Eval',
- inSignature: 's',
- outSignature: 'bs'
- },
- { name: 'ListExtensions',
- inSignature: '',
- outSignature: 'a{sa{sv}}'
- },
- { name: 'GetExtensionInfo',
- inSignature: 's',
- outSignature: 'a{sv}'
- },
- { name: 'GetExtensionErrors',
- inSignature: 's',
- outSignature: 'as'
- },
- { name: 'ScreenshotArea',
- inSignature: 'iiiis',
- outSignature: 'b'
- },
- { name: 'ScreenshotWindow',
- inSignature: 'bs',
- outSignature: 'b'
- },
- { name: 'Screenshot',
- inSignature: 's',
- outSignature: 'b'
- },
- { name: 'EnableExtension',
- inSignature: 's',
- outSignature: ''
- },
- { name: 'DisableExtension',
- inSignature: 's',
- outSignature: ''
- },
- { name: 'InstallRemoteExtension',
- inSignature: 'ss',
- outSignature: ''
- },
- { name: 'UninstallExtension',
- inSignature: 's',
- outSignature: 'b'
- }
- ],
- signals: [{ name: 'ExtensionStatusChanged',
- inSignature: 'sis' }],
- properties: [{ name: 'OverviewActive',
- signature: 'b',
- access: 'readwrite' },
- { name: 'ApiVersion',
- signature: 'i',
- access: 'read' },
- { name: 'ShellVersion',
- signature: 's',
- access: 'read' }]
-};
+const GnomeShellIface = <interface name="org.gnome.Shell">
+<method name="Eval">
+ <arg type="s" direction="in" name="script" />
+ <arg type="b" direction="out" name="success" />
+ <arg type="s" direction="out" name="result" />
+</method>
+<method name="ListExtensions">
+ <arg type="a{sa{sv}}" direction="out" name="extensions" />
+</method>
+<method name="GetExtensionInfo">
+ <arg type="s" direction="in" name="extension" />
+ <arg type="a{sv}" direction="out" name="info" />
+</method>
+<method name="GetExtensionErrors">
+ <arg type="s" direction="in" name="extension" />
+ <arg type="as" direction="out" name="errors" />
+</method>
+<method name="ScreenshotArea">
+ <arg type="i" direction="in" name="x"/>
+ <arg type="i" direction="in" name="y"/>
+ <arg type="i" direction="in" name="width"/>
+ <arg type="i" direction="in" name="height"/>
+ <arg type="s" direction="in" name="filename"/>
+ <arg type="b" direction="out" name="success"/>
+</method>
+<method name="ScreenshotWindow">
+ <arg type="b" direction="in" name="include_frame"/>
+ <arg type="s" direction="in" name="filename"/>
+ <arg type="b" direction="out" name="success"/>
+</method>
+<method name="Screenshot">
+ <arg type="s" direction="in" name="filename"/>
+ <arg type="b" direction="out" name="success"/>
+</method>
+<method name="EnableExtension">
+ <arg type="s" direction="in" name="uuid"/>
+</method>
+<method name="DisableExtension">
+ <arg type="s" direction="in" name="uuid"/>
+</method>
+<method name="InstallRemoteExtension">
+ <arg type="s" direction="in" name="uuid"/>
+ <arg type="s" direction="in" name="version"/>
+</method>
+<method name="UninstallExtension">
+ <arg type="s" direction="in" name="uuid"/>
+ <arg type="b" direction="out" name="success"/>
+</method>
+<property name="OverviewActive" type="b" access="readwrite" />
+<property name="ApiVersion" type="i" access="read" />
+<property name="ShellVersion" type="s" access="read" />
+<signal name="ExtensionStatusChanged">
+ <arg type="s" name="uuid"/>
+ <arg type="i" name="state"/>
+ <arg type="s" name="error"/>
+</signal>
+</interface>;
function GnomeShell() {
this._init();
GnomeShell.prototype = {
_init: function() {
- DBus.session.exportObject('/org/gnome/Shell', this);
+ this._dbusImpl = Gio.DBusExportedObject.wrapJSObject(GnomeShellIface, this);
+ this._dbusImpl.export(Gio.DBus.session, '/org/gnome/Shell');
ExtensionSystem.connect('extension-state-changed',
Lang.bind(this, this._extensionStateChanged));
},
},
ListExtensions: function() {
- return ExtensionSystem.extensionMeta;
+ let out;
+ for (let uuid in ExtensionSystem.extensionMeta) {
+ let dbusObj = this.GetExtensionInfo(uuid);
+ out[uuid] = dbusObj;
+ }
+ return out;
},
GetExtensionInfo: function(uuid) {
- return ExtensionSystem.extensionMeta[uuid] || {};
+ let meta = ExtensionSystem.extensionMeta[uuid] || {};
+ let out;
+ for (let key in meta) {
+ let val = meta[key];
+ let type;
+ switch (typeof val) {
+ case 'object':
+ throw Error('Extension had a nested object in the metadata. This is not supported');
+ case 'string':
+ type = 's';
+ break;
+ case 'number':
+ type = 'd';
+ break;
+ }
+ out[key] = GLib.Variant.new(type, val);
+ }
+ return out;
},
GetExtensionErrors: function(uuid) {
[newState.uuid, newState.state, newState.error]);
}
};
-
-DBus.conformExport(GnomeShell.prototype, GnomeShellIface);
-
#include <cogl-pango/cogl-pango.h>
#include <clutter/clutter.h>
#include <clutter/x11/clutter-x11.h>
-#include <dbus/dbus-glib.h>
#include <gdk/gdk.h>
#include <gdk/gdkx.h>
#include <gtk/gtk.h>
static gboolean is_gdm_mode = FALSE;
+#define DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER 1
+#define DBUS_REQUEST_NAME_REPLY_ALREADY_OWNER 4
+
static void
-shell_dbus_acquire_name (DBusGProxy *bus,
+shell_dbus_acquire_name (GDBusProxy *bus,
guint32 request_name_flags,
guint32 *request_name_result,
gchar *name,
gboolean fatal)
{
GError *error = NULL;
- if (!dbus_g_proxy_call (bus, "RequestName", &error,
- G_TYPE_STRING, name,
- G_TYPE_UINT, request_name_flags,
- G_TYPE_INVALID,
- G_TYPE_UINT, request_name_result,
- G_TYPE_INVALID))
+ GVariant *request_name_variant;
+
+ if (!(request_name_variant = g_dbus_proxy_call_sync (bus,
+ "RequestName",
+ g_variant_new ("(su)", name, request_name_flags),
+ 0, /* call flags */
+ -1, /* timeout */
+ NULL, /* cancellable */
+ &error)))
{
- g_printerr ("failed to acquire %s: %s\n", name, error->message);
- if (fatal)
- exit (1);
+ g_printerr ("failed to acquire org.gnome.Shell: %s\n", error->message);
+ exit (1);
}
+ g_variant_get (request_name_variant, "(u)", request_name_result);
}
static void
-shell_dbus_acquire_names (DBusGProxy *bus,
+shell_dbus_acquire_names (GDBusProxy *bus,
guint32 request_name_flags,
gchar *name,
gboolean fatal, ...) G_GNUC_NULL_TERMINATED;
static void
-shell_dbus_acquire_names (DBusGProxy *bus,
+shell_dbus_acquire_names (GDBusProxy *bus,
guint32 request_name_flags,
gchar *name,
gboolean fatal, ...)
static void
shell_dbus_init (gboolean replace)
{
- DBusGConnection *session;
- DBusGProxy *bus;
+ GDBusConnection *session;
+ GDBusProxy *bus;
+ GError *error = NULL;
guint32 request_name_flags;
guint32 request_name_result;
- /* TODO:
- * In the future we should use GDBus for this. However, in
- * order to do that, we need to port all of the JavaScript
- * code. Otherwise, the name will be claimed on the wrong
- * connection.
- */
- session = dbus_g_bus_get (DBUS_BUS_SESSION, NULL);
+ session = g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, &error);
- bus = dbus_g_proxy_new_for_name (session,
- DBUS_SERVICE_DBUS,
- DBUS_PATH_DBUS,
- DBUS_INTERFACE_DBUS);
+ if (error) {
+ g_printerr ("Failed to connect to session bus: %s", error->message);
+ exit (1);
+ }
+
+ bus = g_dbus_proxy_new_sync (session,
+ G_DBUS_PROXY_FLAGS_NONE,
+ NULL, /* interface info */
+ "org.freedesktop.DBus",
+ "/org/freedesktop/DBus",
+ "org.freedesktop.DBus",
+ NULL, /* cancellable */
+ &error);
- request_name_flags = DBUS_NAME_FLAG_DO_NOT_QUEUE | DBUS_NAME_FLAG_ALLOW_REPLACEMENT;
+ request_name_flags = G_BUS_NAME_OWNER_FLAGS_ALLOW_REPLACEMENT;
if (replace)
request_name_flags |= DBUS_NAME_FLAG_REPLACE_EXISTING;
+
shell_dbus_acquire_name (bus,
request_name_flags,
&request_name_result,
if (!(request_name_result == DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER
|| request_name_result == DBUS_REQUEST_NAME_REPLY_ALREADY_OWNER))
{
- g_printerr ("%s already exists on bus and --replace not specified\n",
- SHELL_DBUS_SERVICE);
+ g_printerr (SHELL_DBUS_SERVICE " already exists on bus and --replace not specified\n");
exit (1);
}
* We always specify REPLACE_EXISTING to ensure we kill off
* the existing service if it was running.
*/
- request_name_flags |= DBUS_NAME_FLAG_REPLACE_EXISTING;
+ request_name_flags |= G_BUS_NAME_OWNER_FLAGS_REPLACE;
+
shell_dbus_acquire_names (bus,
request_name_flags,
/* Also grab org.gnome.Panel to replace any existing panel process */
&request_name_result,
"org.gnome.Caribou.Keyboard", FALSE);
g_object_unref (bus);
+ g_object_unref (session);
}
static void